package main

import (
	"fmt"
)

/**
 * @Author: DengLibin
 * @Date: Create in 2023-01-17 13:33:15
 * @Description:
 */
/**
* @Author: DengLibin
* @Date: Create in 2023-01-17 13:33:45
* @Description: 思路： 一共10个灯，对应10个二进制位 n个灯亮，求出n个灯亮的所有组合(0-9取n， 如: n=3,组合有:012,013,014..., 023...,034...)
 遍历每个组合,将每个组合中对应的二进制位设置为1（开灯）如: 012这个组合 把0，1，2三位设置为1，则二进制表示为00_0000_0111， 013：00_0000_1011
 再对二进制位分别取高4位和低6位作为小时数和分钟数，如果是合法的小时数和分钟数则 当前结果满足条件
*/
func readBinaryWatch(turnedOn int) []string {
	if turnedOn == 0 {
		return []string{"0:00"}
	}
	//最多8个
	if turnedOn > 8 {
		return []string{}
	}
	//高4位表示小时,低6位表示分钟
	//led := 0b_0000_0000_00

	arr := make([]string, 0)
	//求0-9所有组合
	dfsNum(0, 0, turnedOn, "", &arr)

	return arr
}

/**
 * @Author: DengLibin
 * @Date: Create in 2023-01-17 14:12:00
 * @Description: 0-9 任意n个数的所有组合
 * @param start 当前层开始的那个数
 * @param currentDeep 当前第几层 0开始
 * @param n 共多少层 （最大深度）
 */
func dfsNum(start, currentDeep, n int, s string, arr *[]string) {
	if currentDeep == n {
		//*arr = append(*arr, s)
		//将对应位置的的二进制位置为1
		b := byte(s[0]) - 48
		x := 1 << b
		for i := 1; i < len(s); i++ {
			b = byte(s[i]) - 48
			t := 1 << b
			x = x | t
		}
		h := x >> 6               //小时 高4位
		min := x & 0b_0000_111111 //分钟 低6位
		if h >= 0 && h <= 11 && min >= 0 && min <= 59 {
			*arr = append(*arr, fmt.Sprintf("%d:%02d", h, min))
		}
		return
	}
	for i := start; i <= 10-n+currentDeep; i++ {
		ss := fmt.Sprintf("%s%d", s, i)
		dfsNum(i+1, currentDeep+1, n, ss, arr)
	}
}

/**
 * @Author: DengLibin
 * @Date: Create in 2023-01-17 14:12:00
 * @Description: 0-9 任意n个数的所有组合
 */
func dfs(start, currentDeep, n int, s string, arr *[]string) {
	if currentDeep == n {
		*arr = append(*arr, s)
		return
	}
	for i := start; i <= 10-n+currentDeep; i++ {
		ss := fmt.Sprintf("%s%d", s, i)
		dfs(i+1, currentDeep+1, n, ss, arr)
	}
}
